package com.edfeff.bio.adapter;

import com.edfeff.bio.http.IAdapter;
import com.edfeff.bio.http.Request;
import com.edfeff.bio.http.Response;

import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.net.URL;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.security.CodeSource;

/**
 * 文件服务
 */
public class FileAdapter implements IAdapter {
    private static Path basePath;

    static {
        try {
            //设置文件服务根路径
            CodeSource codeSource = FileAdapter.class.getProtectionDomain().getCodeSource();
            URL location = codeSource.getLocation();
            Path baseDir = Paths.get(location.toURI());//.getParent().getParent();
            baseDir = baseDir.resolve("static");
            basePath = baseDir.toAbsolutePath();
            System.out.println("文件服务根路径=" + baseDir);
        } catch (Exception e) {
            throw new RuntimeException("必须设置文件根路径");
        }
    }

    @Override
    public void service(Request req, Response res) throws Exception {
        String uri = req.getUri();
        Path staticFile = getFilePath(uri);
        File file = staticFile.toFile();
        if (file.exists() && file.isFile()) {
            writeFile(file, res);
        } else {
            write404(res);
        }
    }

    private void writeFile(File file, Response res) {
        try {
            FileInputStream fin = new FileInputStream(file);
            ByteArrayOutputStream out = new ByteArrayOutputStream();
            byte[] buf = new byte[8 * 1024];
            int n = -1;
            while ((n = fin.read(buf)) > 0) {
                out.write(buf, 0, n);
            }
            out.flush();

            byte[] bytes = out.toByteArray();
            res.setBody(bytes);

            fin.close();
            out.close();
        } catch (Exception e) {
            res.setStatus(500);
            res.setStringBody("internal error.");
        }
    }

    private void write404(Response res) {
        res.setStatus(404);
        res.setStringBody("file not exists.");
    }

    public Path getFilePath(String uri) {
        if (uri.startsWith("/")) {
            uri = uri.substring(1);
        }
        if ("".equals(uri)) {
            uri = "index.html";
        }
        return basePath.resolve(uri);
    }
}
